/**
 * Copyright (C) 2023 maminjie <canpool@163.com>
 * Copyright (C) 2017 Uwe Kindler
 * SPDX-License-Identifier: LGPL-2.1
 **/
#pragma once

#include "QxDockContainerWidget.h"
#include "QxDockWidget.h"
#include "QxDockFloatingContainer.h"
#include "QxDockGlobal.h"

QT_FORWARD_DECLARE_CLASS(QSettings)
QT_FORWARD_DECLARE_CLASS(QMenu)

QX_BEGIN_NAMESPACE

struct DockManagerPrivate;
class DockFloatingContainer;
struct DockFloatingContainerPrivate;
class DockContainerWidget;
class DockContainerWidgetPrivate;
class DockOverlay;
class DockAreaTabBar;
class DockWidgetTab;
struct DockWidgetTabPrivate;
struct DockAreaWidgetPrivate;
class DockIconProvider;
class DockComponentsFactory;
class DockFocusController;
class DockAutoHideSideBar;

/**
 * The central dock manager that maintains the complete docking system.
 * With the configuration flags you can globally control the functionality
 * of the docking system. The dock manager uses an internal stylesheet to
 * style its components like splitters, tabs and buttons. If you want to
 * disable this stylesheet because your application uses its own,
 * just call the function for settings the stylesheet with an empty
 * string.
 * \code
 * dockManager->setStyleSheet("");
 * \endcode
 **/
class QX_DOCK_EXPORT DockManager : public DockContainerWidget
{
    Q_OBJECT
private:
    DockManagerPrivate *d;   ///< private data (pimpl)
    friend struct DockManagerPrivate;
    friend class DockFloatingContainer;
    friend struct DockFloatingContainerPrivate;
    friend class DockContainerWidget;
    friend class DockContainerWidgetPrivate;
    friend class DockAreaTabBar;
    friend class DockWidgetTab;
    friend struct DockAreaWidgetPrivate;
    friend struct DockWidgetTabPrivate;
    friend class DockFloatingDragPreview;
    friend struct DockFloatingDragPreviewPrivate;
    friend class DockAreaTitleBar;
    friend class DockAutoHideContainer;
    friend DockAutoHideSideBar;

public Q_SLOTS:
    /**
     * Ends the isRestoringFromMinimizedState
     */
    void endLeavingMinimizedState();
protected:
    /**
     * Registers the given floating widget in the internal list of
     * floating widgets
     */
    void registerFloatingWidget(DockFloatingContainer *FloatingWidget);

    /**
     * Remove the given floating widget from the list of registered floating
     * widgets
     */
    void removeFloatingWidget(DockFloatingContainer *FloatingWidget);

    /**
     * Registers the given dock container widget
     */
    void registerDockContainer(DockContainerWidget *DockContainer);

    /**
     * Remove dock container from the internal list of registered dock
     * containers
     */
    void removeDockContainer(DockContainerWidget *DockContainer);

    /**
     * Overlay for containers
     */
    DockOverlay *containerOverlay() const;

    /**
     * Overlay for dock areas
     */
    DockOverlay *dockAreaOverlay() const;

    /**
     * A container needs to call this function if a widget has been dropped
     * into it
     */
    void notifyWidgetOrAreaRelocation(QWidget *RelocatedWidget);

    /**
     * This function is called, if a floating widget has been dropped into
     * an new position.
     * When this function is called, all dock widgets of the FloatingWidget
     * are already inserted into its new position
     */
    void notifyFloatingWidgetDrop(DockFloatingContainer *FloatingWidget);

    /**
     * Show the floating widgets that has been created floating
     */
    virtual void showEvent(QShowEvent *event) override;

    /**
     * Acces for the internal dock focus controller.
     * This function only returns a valid object, if the FocusHighlighting
     * flag is set.
     */
    DockFocusController *dockFocusController() const;

    /**
     * Restore floating widgets hidden by an earlier call to hideManagerAndFloatingWidgets.
     */
    void restoreHiddenFloatingWidgets();
public:
    using Super = DockContainerWidget;

    enum eViewMenuInsertionOrder {
        MenuSortedByInsertion,
        MenuAlphabeticallySorted
    };

    /**
     * These global configuration flags configure some global dock manager
     * settings.
     * Set the dock manager flags, before you create the dock manager instance.
     */
    enum eConfigFlag {
        ActiveTabHasCloseButton = 0x0001,   //!< If this flag is set, the active tab in a tab area has a close button
        DockAreaHasCloseButton = 0x0002,    //!< If the flag is set each dock area has a close button
        DockAreaCloseButtonClosesTab = 0x0004,   //!< If the flag is set, the dock area close button closes the active
                                                 //!< tab, if not set, it closes the complete dock area
        OpaqueSplitterResize = 0x0008,           //!< See QSplitter::setOpaqueResize() documentation
        XmlAutoFormattingEnabled = 0x0010,       //!< If enabled, the XML writer automatically adds line-breaks and
                                             //!< indentation to empty sections between elements (ignorable whitespace).
        XmlCompressionEnabled =
            0x0020,   //!< If enabled, the XML output will be compressed and is not human readable anymore
        TabCloseButtonIsToolButton = 0x0040,   //! If enabled the tab close buttons will be QToolButtons instead of
                                               //! QPushButtons - disabled by default
        AllTabsHaveCloseButton = 0x0080,   //!< if this flag is set, then all tabs that are closable show a close button
        RetainTabSizeWhenCloseButtonHidden = 0x0100,   //!< if this flag is set, the space for the close button is
                                                       //!< reserved even if the close button is not visible
        DragPreviewIsDynamic =
            0x0400,   ///< If opaque undocking is disabled, this flag defines the behavior of the drag preview window,
                      ///< if this flag is enabled, the preview will be adjusted dynamically to the drop area
        DragPreviewShowsContentPixmap =
            0x0800,   ///< If opaque undocking is disabled, the created drag preview window shows a copy of the content
                      ///< of the dock widget / dock are that is dragged
        DragPreviewHasWindowFrame = 0x1000,   ///< If opaque undocking is disabled, then this flag configures if the
                                              ///< drag preview is frameless or looks like a real window
        AlwaysShowTabs = 0x2000,   ///< If this option is enabled, the tab of a dock widget is always displayed - even
                                   ///< if it is the only visible dock widget in a floating widget.
        DockAreaHasUndockButton = 0x4000,        //!< If the flag is set each dock area has an undock button
        DockAreaHasTabsMenuButton = 0x8000,      //!< If the flag is set each dock area has a tabs menu button
        DockAreaHideDisabledButtons = 0x10000,   //!< If the flag is set disabled dock area buttons will not appear on
                                                 //!< the toolbar at all (enabling them will bring them back)
        DockAreaDynamicTabsMenuButtonVisibility =
            0x20000,   //!< If the flag is set, the tabs menu button will be shown only when it is required - that
                       //!< means, if the tabs are elided. If the tabs are not elided, it is hidden
        FloatingContainerHasWidgetTitle =
            0x40000,   //!< If set, the Floating Widget window title reflects the title of the current dock widget
                       //!< otherwise it displays the title set with `DockManager::setFloatingContainersTitle` or
                       //!< application name as window title
        FloatingContainerHasWidgetIcon = 0x80000,   //!< If set, the Floating Widget icon reflects the icon of the
                                                    //!< current dock widget otherwise it displays application icon
        HideSingleCentralWidgetTitleBar =
            0x100000,   //!< If there is only one single visible dock widget in the main dock container (the dock
                        //!< manager) and if this flag is set, then the titlebar of this dock widget will be hidden this
                        //!< only makes sense for non draggable and non floatable widgets and enables the creation of
                        //!< some kind of "central" widget

        FocusHighlighting = 0x200000,   //!< enables styling of focused dock widget tabs or floating widget titlebar
        EqualSplitOnInsertion =
            0x400000,                   ///!< if enabled, the space is equally distributed to all widgets in a  splitter

        FloatingContainerForceNativeTitleBar =
            0x800000,   //!< Linux only ! Forces all FloatingContainer to use the native title bar. This might break
                        //!< docking for FloatinContainer on some Window Managers (like Kwin/KDE). If neither this nor
                        //!< FloatingContainerForceCustomTitleBar is set (the default) native titlebars are used except
                        //!< on known bad systems.
                        //! Users can overwrite this by setting the environment variable ADS_UseNativeTitle to "1" or
                        //! "0".
        FloatingContainerForceQWidgetTitleBar =
            0x1000000,   //!< Linux only ! Forces all FloatingContainer to use a QWidget based title bar.
                         //!< If neither this nor FloatingContainerForceNativeTitleBar is set (the default) native
                         //!< titlebars are used except on known bad systems.
                         //! Users can overwrite this by setting the environment variable ADS_UseNativeTitle to "1" or
                         //! "0".
        MiddleMouseButtonClosesTab = 0x2000000,   //! If the flag is set, the user can use the mouse middle button to
                                                  //! close the tab under the mouse

        DefaultDockAreaButtons = DockAreaHasCloseButton | DockAreaHasUndockButton |
                                 DockAreaHasTabsMenuButton,   ///< default configuration of dock area title bar buttons

        DefaultBaseConfig = DefaultDockAreaButtons | ActiveTabHasCloseButton | XmlCompressionEnabled |
                            FloatingContainerHasWidgetTitle,   ///< default base configuration settings

        DefaultOpaqueConfig = DefaultBaseConfig | OpaqueSplitterResize |
                              DragPreviewShowsContentPixmap,   ///< the default configuration for non opaque operations

        DefaultNonOpaqueConfig =
            DefaultBaseConfig |
            DragPreviewShowsContentPixmap,   ///< the default configuration for non opaque operations

        NonOpaqueWithWindowFrame =
            DefaultNonOpaqueConfig | DragPreviewHasWindowFrame   ///< the default configuration for non opaque
                                                                 ///< operations that show a real window with frame
    };
    Q_DECLARE_FLAGS(ConfigFlags, eConfigFlag)

    /**
     * These global configuration flags configure some dock manager auto hide
     * settings
     * Set the dock manager flags, before you create the dock manager instance.
     */
    enum eAutoHideFlag {
        AutoHideFeatureEnabled = 0x01,      //!< enables / disables auto hide feature
        DockAreaHasAutoHideButton = 0x02,   //!< If the flag is set each dock area has a auto hide menu button
        AutoHideButtonTogglesArea =
            0x04,   //!< If the flag is set, the auto hide button enables auto hiding for all dock widgets in an area,
                    //!< if disabled, only the current dock widget will be toggled
        AutoHideButtonCheckable = 0x08,   //!< If the flag is set, the auto hide button will be checked and unchecked
                                          //!< depending on the auto hide state. Mainly for styling purposes.
        AutoHideSideBarsIconOnly =
            0x10,   ///< show only icons in auto hide side tab - if a tab has no icon, then the text will be shown
        AutoHideShowOnMouseOver =
            0x20,   ///< show the auto hide window on mouse over tab and hide it if mouse leaves auto hide container
        AutoHideCloseButtonCollapsesDock =
            0x40,   ///< Close button of an auto hide container collapses the dock instead of hiding it completely

        DefaultAutoHideConfig = AutoHideFeatureEnabled |
                                DockAreaHasAutoHideButton   ///< the default configuration for left and right side bars
    };
    Q_DECLARE_FLAGS(AutoHideFlags, eAutoHideFlag)

    /**
     * Default Constructor.
     * If the given parent is a QMainWindow, the dock manager sets itself as the
     * central widget.
     * Before you create any dock widgets, you should properly setup the
     * configuration flags via setConfigFlags().
     */
    DockManager(QWidget *parent = nullptr);

    /**
     * Virtual Destructor
     */
    virtual ~DockManager() override;

    /**
     * This function returns the global configuration flags
     */
    static ConfigFlags configFlags();

    /**
     * This function returns the auto hide configuration flags
     */
    static AutoHideFlags autoHideConfigFlags();

    /**
     * Sets the global configuration flags for the whole docking system.
     * Call this function before you create the dock manager and before
     * your create the first dock widget.
     */
    static void setConfigFlags(const ConfigFlags Flags);

    /**
     * Sets the global configuration flags for the whole docking system.
     * Call this function before you create the dock manager and before
     * your create the first dock widget.
     */
    static void setAutoHideConfigFlags(const AutoHideFlags Flags);

    /**
     * Set a certain config flag.
     * \see setConfigFlags()
     */
    static void setConfigFlag(eConfigFlag Flag, bool On = true);

    /**
     * Set a certain overlay config flag.
     * \see setConfigFlags()
     */
    static void setAutoHideConfigFlag(eAutoHideFlag Flag, bool On = true);

    /**
     * Returns true if the given config flag is set
     */
    static bool testConfigFlag(eConfigFlag Flag);

    /**
     * Returns true if the given overlay config flag is set
     */
    static bool testAutoHideConfigFlag(eAutoHideFlag Flag);

    /**
     * Returns the global icon provider.
     * The icon provider enables the use of custom icons in case using
     * styleheets for icons is not an option.
     */
    static DockIconProvider &iconProvider();

    /**
     * Adds dockwidget into the given area.
     * If DockAreaWidget is not null, then the area parameter indicates the area
     * into the DockAreaWidget. If DockAreaWidget is null, the Dockwidget will
     * be dropped into the container. If you would like to add a dock widget
     * tabified, then you need to add it to an existing dock area object
     * into the CenterDockWidgetArea. The following code shows this:
     * \code
     * dockManager->addDockWidget(Qx::CenterDockWidgetArea, NewDockWidget,
     * 	   ExisitingDockArea);
     * \endcode
     * \return Returns the dock area widget that contains the new dockWidget
     */
    DockAreaWidget *addDockWidget(DockWidgetArea area, DockWidget *dockwidget,
                                   DockAreaWidget *dockAreaWidget = nullptr, int Index = -1);

    /**
     * Adds dockwidget into the given container.
     * This allows you to place the dock widget into a container, even if that
     * container does not yet contain a DockAreaWidget.
     * \return Returns the dock area widget that contains the new dockWidget
     */
    DockAreaWidget *addDockWidgetToContainer(DockWidgetArea area, DockWidget *dockwidget,
                                              DockContainerWidget *dockContainerWidget);

    /**
     * Adds an Auto-Hide widget to the dock manager container pinned to
     * the given side bar location.
     * \return Returns the DockAutoHideContainer that contains the new dockWidget
     */
    DockAutoHideContainer *addAutoHideDockWidget(SideBarLocation Location, DockWidget *dockwidget);

    /**
     * Adds an Auto-Hide widget to the given DockContainerWidget pinned to
     * the given side bar location in this container.
     * \return Returns the DockAutoHideContainer that contains the new dockWidget
     */
    DockAutoHideContainer *addAutoHideDockWidgetToContainer(SideBarLocation Location, DockWidget *dockwidget,
                                                             DockContainerWidget *dockContainerWidget);

    /**
     * This function will add the given Dockwidget to the given dock area as
     * a new tab.
     * If no dock area widget exists for the given area identifier, a new
     * dock area widget is created.
     */
    DockAreaWidget *addDockWidgetTab(DockWidgetArea area, DockWidget *dockwidget);

    /**
     * This function will add the given Dockwidget to the given DockAreaWidget
     * as a new tab.
     * If index is out of range, the tab is simply appended. Otherwise it is
     * inserted at the specified position.
     */
    DockAreaWidget *addDockWidgetTabToArea(DockWidget *dockwidget, DockAreaWidget *dockAreaWidget, int Index = -1);

    /**
     * Adds the given dockWidget floating and returns the created
     * DockFloatingContainer instance.
     */
    DockFloatingContainer *addDockWidgetFloating(DockWidget *dockwidget);

    /**
     * Searches for a registered doc widget with the given ObjectName
     * \return Return the found dock widget or nullptr if a dock widget with the
     * given name is not registered
     */
    DockWidget *findDockWidget(const QString &ObjectName) const;

    /**
     * Remove the given Dock from the dock manager
     */
    void removeDockWidget(DockWidget *dockwidget);

    /**
     * This function returns a readable reference to the internal dock
     * widgets map so that it is possible to iterate over all dock widgets
     */
    QMap<QString, DockWidget *> dockWidgetsMap() const;

    /**
     * Returns the list of all active and visible dock containers
     * Dock containers are the main dock manager and all floating widgets
     */
    const QList<DockContainerWidget *> dockContainers() const;

    /**
     * Returns the list of all floating widgets
     */
    const QList<DockFloatingContainer *> floatingWidgets() const;

    /**
     * This function always return 0 because the main window is always behind
     * any floating widget
     */
    unsigned int zOrderIndex() const override;

    /**
     * Saves the current state of the dockmanger and all its dock widgets
     * into the returned QByteArray.
     * The XmlMode enables / disables the auto formatting for the XmlStreamWriter.
     * If auto formatting is enabled, the output is intended and line wrapped.
     * The XmlMode XmlAutoFormattingDisabled is better if you would like to have
     * a more compact XML output - i.e. for storage in ini files.
     * The version number is stored as part of the data.
     * To restore the saved state, pass the return value and version number
     * to restoreState().
     * \see restoreState()
     */
    QByteArray saveState(int version = 0) const;

    /**
     * Restores the state of this dockmanagers dockwidgets.
     * The version number is compared with that stored in state. If they do
     * not match, the dockmanager's state is left unchanged, and this function
     * returns false; otherwise, the state is restored, and this function
     * returns true.
     * \see saveState()
     */
    bool restoreState(const QByteArray &state, int version = 0);

    /**
     * Saves the current perspective to the internal list of perspectives.
     * A perspective is the current state of the dock manager assigned
     * with a certain name. This makes it possible for the user,
     * to switch between different perspectives quickly.
     * If a perspective with the given name already exists, then
     * it will be overwritten with the new state.
     */
    void addPerspective(const QString &UniquePrespectiveName);

    /**
     * Removes the perspective with the given name from the list of perspectives
     */
    void removePerspective(const QString &Name);

    /**
     * Removes the given perspectives from the dock manager
     */
    void removePerspectives(const QStringList &Names);

    /**
     * Returns the names of all available perspectives
     */
    QStringList perspectiveNames() const;

    /**
     * Saves the perspectives to the given settings file.
     */
    void savePerspectives(QSettings &Settings) const;

    /**
     * Loads the perspectives from the given settings file
     */
    void loadPerspectives(QSettings &Settings);

    /**
     * This function returns managers central widget or nullptr if no central widget is set.
     */
    DockWidget *centralWidget() const;

    /**
     * Adds dockwidget widget into the central area and marks it as central widget.
     * If central widget is set, it will be the only dock widget
     * that will resize with the dock container. A central widget if not
     * movable, floatable or closable and the titlebar of the central
     * dock area is not visible.
     * If the given widget could be set as central widget, the function returns
     * the created dock area. If the widget could not be set, because there
     * is already a central widget, this function returns a nullptr.
     * To clear the central widget, pass a nullptr to the function.
     * \note Setting a central widget is only possible if no other dock widgets
     * have been registered before. That means, this function should be the
     * first function that you call before you add other dock widgets.
     * \retval != 0 The dock area that contains the central widget
     * \retval nullptr Indicates that the given widget can not be set as central
     *         widget because there is already a central widget.
     */
    DockAreaWidget *setCentralWidget(DockWidget *widget);

    /**
     * Adds a toggle view action to the the internal view menu.
     * You can either manage the insertion of the toggle view actions in your
     * application or you can add the actions to the internal view menu and
     * then simply insert the menu object into your.
     * \param[in] ToggleViewAction The action to insert. If no group is provided
     *            the action is directly inserted into the menu. If a group
     *            is provided, the action is inserted into the group and the
     *            group is inserted into the menu if it is not existing yet.
     * \param[in] Group This is the text used for the group menu item
     * \param[in] GroupIcon The icon used for grouping the workbenches in the
     *            view menu. I.e. if there is a workbench for each device
     *            like for spectrometer devices, it is good to group all these
     *            workbenches under a menu item
     * \return If Group is not empty, this function returns the GroupAction
     *         for this group. If the group is empty, the function returns
     *         the given ToggleViewAction.
     */
    QAction *addToggleViewActionToMenu(QAction *ToggleViewAction, const QString &Group = QString(),
                                       const QIcon &GroupIcon = QIcon());

    /**
     * This function returns the internal view menu.
     * To fill the view menu, you can use the addToggleViewActionToMenu()
     * function.
     */
    QMenu *viewMenu() const;

    /**
     * Define the insertion order for toggle view menu items.
     * The order defines how the actions are added to the view menu.
     * The default insertion order is MenuAlphabeticallySorted to make it
     * easier for users to find the menu entry for a certain dock widget.
     * You need to call this function befor you insert the first menu item
     * into the view menu.
     */
    void setViewMenuInsertionOrder(eViewMenuInsertionOrder Order);

    /**
     * This function returns true between the restoringState() and
     * stateRestored() signals.
     */
    bool isRestoringState() const;

    /**
     * This function returns true, if the dockManager window is restoring from
     * minimized state.
     * The dockManager is in this state starting from the QWindowStateChangeEvent
     * that signals the state change from minimized to normal until
     * endLeavingMinimizedState() function is called.
     */
    bool isLeavingMinimizedState() const;

    /**
     * The distance the user needs to move the mouse with the left button
     * hold down before a dock widget start floating
     */
    static int startDragDistance();

    /**
     * Helper function to set focus depending on the configuration of the
     * FocusStyling flag
     */
    template <class QWidgetPtr> static void setWidgetFocus(QWidgetPtr widget)
    {
        if (!DockManager::testConfigFlag(DockManager::FocusHighlighting)) {
            return;
        }

        widget->setFocus(Qt::OtherFocusReason);
    }

    bool eventFilter(QObject *obj, QEvent *e) override;

    /**
     * Returns the dock widget that has focus style in the ui or a nullptr if
     * not dock widget is painted focused.
     * If the flag FocusHighlighting is disabled, this function always returns
     * nullptr.
     */
    DockWidget *focusedDockWidget() const;

    /**
     * Returns the sizes of the splitter that contains the dock area.
     *
     * If there is no splitter that contains the area, an empty list will be
     * returned.
     */
    QList<int> splitterSizes(DockAreaWidget *ContainedArea) const;

    /**
     * Update the sizes of a splitter
     * Programmatically updates the sizes of a given splitter by calling
     * QSplitter::setSizes(). The splitter will be the splitter that
     * contains the supplied dock area widget. If there is not splitter
     * that contains the dock area, or the sizes supplied does not match
     * the number of children of the splitter, this method will have no
     * effect.
     */
    void setSplitterSizes(DockAreaWidget *ContainedArea, const QList<int> &sizes);

    /**
     * Set a custom title for all FloatingContainer that does not reflect
     * the title of the current dock widget.
     */
    static void setFloatingContainersTitle(const QString &Title);

    /**
     * Returns the title used by all FloatingContainer that does not
     * reflect the title of the current dock widget.
     *
     * If not title was set with setFloatingContainersTitle(), it returns
     * QGuiApplication::applicationDisplayName().
     */
    static QString floatingContainersTitle();

public Q_SLOTS:
    /**
     * Opens the perspective with the given name.
     */
    void openPerspective(const QString &PerspectiveName);

    /**
     * Request a focus change to the given dock widget.
     * This function only has an effect, if the flag DockManager::FocusStyling
     * is enabled
     */
    void setDockWidgetFocused(DockWidget *dockWidget);

    /**
     * hide DockManager and all floating widgets (See Issue #380). Calling regular QWidget::hide()
     * hides the DockManager but not the floating widgets;
     */
    void hideManagerAndFloatingWidgets();

Q_SIGNALS:
    /**
     * This signal is emitted if the list of perspectives changed.
     * The list of perspectives changes if perspectives are added, removed
     * or if the perspective list has been loaded
     */
    void perspectiveListChanged();

    /**
     * This signal is emitted if the perspective list has been loaded
     */
    void perspectiveListLoaded();

    /**
     * This signal is emitted if perspectives have been removed
     */
    void perspectivesRemoved();

    /**
     * This signal is emitted, if the restore function is called, just before
     * the dock manager starts restoring the state.
     * If this function is called, nothing has changed yet
     */
    void restoringState();

    /**
     * This signal is emitted if the state changed in restoreState.
     * The signal is emitted if the restoreState() function is called or
     * if the openPerspective() function is called
     */
    void stateRestored();

    /**
     * This signal is emitted, if the dock manager starts opening a
     * perspective.
     * Opening a perspective may take more than a second if there are
     * many complex widgets. The application may use this signal
     * to show some progress indicator or to change the mouse cursor
     * into a busy cursor.
     */
    void openingPerspective(const QString &PerspectiveName);

    /**
     * This signal is emitted if the dock manager finished opening a
     * perspective.
     */
    void perspectiveOpened(const QString &PerspectiveName);

    /**
     * This signal is emitted, if a new floating widget has been created.
     * An application can use this signal to e.g. subscribe to events of
     * the newly created window.
     */
    void floatingWidgetCreated(Qx::DockFloatingContainer *FloatingWidget);

    /**
     * This signal is emitted, if a new dockArea has been created.
     * An application can use this signal to set custom icons or custom
     * tooltips for the dockArea buttons.
     */
    void dockAreaCreated(Qx::DockAreaWidget *dockArea);

    /**
     * This signal is emitted if a dock widget has been added to this
     * dock manager instance.
     */
    void dockWidgetAdded(Qx::DockWidget *dockWidget);

    /**
     * This signal is emitted just before the given dock widget is removed
     * from the dock manager
     */
    void dockWidgetAboutToBeRemoved(Qx::DockWidget *dockWidget);

    /**
     * This signal is emitted if a dock widget has been removed with the remove
     * removeDockWidget() function.
     * If this signal is emitted, the dock widget has been removed from the
     * docking system but it is not deleted yet.
     */
    void dockWidgetRemoved(Qx::DockWidget *dockWidget);

    /**
     * This signal is emitted if the focused dock widget changed.
     * Both old and now can be nullptr.
     * The focused dock widget is the one that is highlighted in the GUI
     */
    void focusedDockWidgetChanged(Qx::DockWidget *old, Qx::DockWidget *now);
};   // class dockManager

QX_END_NAMESPACE

Q_DECLARE_OPERATORS_FOR_FLAGS(Qx::DockManager::ConfigFlags)

